<template>
  <div class="property-panel" ref="propertyPanel" v-if="element && element.type && element.type !== 'bpmn:Process'">
    <el-form :model="form" label-position="left" size="small" style="margin-top: 15px;" >
      <el-form-item label="节点ID">
        {{form.id}}
      </el-form-item>
      <el-form-item label="节点名称">
        <el-input v-model="form.name" placeholder="请输入节点名称"></el-input>
      </el-form-item>
      <el-form-item v-if="userTask" label="表单布局">
        <el-input placeholder="请选择表单布局" v-model="form.formLayoutName" disabled >
          <el-button slot="append" type="primary" icon="el-icon-search" @click="handleFormLayout"></el-button>
        </el-input>
      </el-form-item>
      <el-form-item v-if="userTask" label="打印布局">
        <el-input placeholder="请选择打印布局" v-model="form.printLayout" disabled >
          <el-button slot="append" type="primary" icon="el-icon-search" @click="handlePrintLayout"></el-button>
        </el-input>
        <!-- <el-input v-model="form.printLayout" placeholder="请输入打印布局" 
          @change="printLayoutChange"></el-input> -->
      </el-form-item>
      <el-form-item label="节点颜色">
        <el-color-picker v-model="form.color" @active-change="colorChange"></el-color-picker>
      </el-form-item>
      <el-divider v-if="userTask" content-position="center">节点操作者</el-divider>
      <!-- 任务节点允许选择人员 -->
      <el-form-item v-if="userTask" label="操作人类型">
        <el-select v-model="form.operator.optType" clearable placeholder="请选择操作者类型" @change="userTypeChange">
          <el-option v-for="(value, key) in userTypeList" :key="key" :label="value" :value="key" />
        </el-select>
      </el-form-item>

      <!-- 指定人员 -->
      <el-form-item label="选择指定人员" v-if="userTask && form.operator.optType === Object.keys(userTypeList)[0]">
        <DeptPositionUser :selectValue="form.operator.data" :multiple="true" mode="free" @valueChange="operatorUserValueChange" />
      </el-form-item>
      <!-- 指定角色 -->
      <el-form-item label="选择指定角色" v-if="userTask && form.operator.optType === Object.keys(userTypeList)[5]">
        <RoleSelect :selectValue="form.operator.data" :multiple="true" @handleChange="roleChange" />
      </el-form-item>
      <!-- 部门 -->
      <el-form-item label="部门" v-if="userTask && [Object.keys(userTypeList)[2], Object.keys(userTypeList)[3]].indexOf(form.operator.optType) >= 0">
        <dept-select :selectValue="form.operator.data" :multiple="true" @valueChange="operatorDeptChange" />
      </el-form-item>
      <!--SQL语句-->
      <el-form-item label="SQL语句" v-if="userTask && form.operator.optType === Object.keys(userTypeList)[4]">
        <el-input
          type="textarea"
          :rows="2"
          placeholder="请输入SQL"
          v-model="form.operator.data"
          @change="operatorSQLChange">
        </el-input>
      </el-form-item>
      <el-divider v-if="userTask"></el-divider>
      <el-form-item v-if="userTask" label="是否回退">
        <el-radio-group v-model="form.isBack" @change="isBackChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="是否指派">
        <el-radio-group v-model="form.isAssignee" @change="isAssigneeChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="是否终止">
        <el-radio-group v-model="form.isClose" @change="isCloseChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="是否签名">
        <el-radio-group v-model="form.isSignature" @change="isSignatureChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="自动流转">
        <el-radio-group v-model="form.isAutoComplete" @change="isAutoCompleteChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-divider v-if="userTask" content-position="center">公示设置</el-divider>
      <el-form-item v-if="userTask" label="是否公示">
        <el-radio-group v-model="form.publicity.isPublicity" @change="publicityChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <template v-if="userTask && form.publicity.isPublicity == 1">
        <el-form-item  label="公示的表单布局">
          <el-input placeholder="请选择表单布局" v-model="form.publicity.layoutName" disabled >
            <el-button slot="append" type="primary" icon="el-icon-search" @click="handleFormLayout('isPublicity')"></el-button>
          </el-input>
        </el-form-item>
      </template>
      <el-divider v-if="userTask" content-position="center">转发设置</el-divider>
      <el-form-item v-if="userTask" label="是否转发">
        <el-radio-group v-model="form.relay.isRelay" @change="relayChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <template v-if="userTask && form.relay.isRelay == 1">
        <el-form-item  label="转发的表单布局">
          <el-input placeholder="请选择表单布局" v-model="form.relay.layoutName" disabled >
            <el-button slot="append" type="primary" icon="el-icon-search" @click="handleFormLayout('isRelay')"></el-button>
          </el-input>
        </el-form-item>
        <!-- 转发人员 -->
        <el-form-item label="自动知会人员">
          <DeptPositionUser :selectValue="form.relay.userList" :multiple="true" @valueChange="relayUserValueChange" />
        </el-form-item>
        <el-form-item label="自动知会人员SQL(与自动知会人员合并)">
          <el-input
            type="textarea"
            :rows="2"
            placeholder="请输入SQL"
            v-model="form.relay.userSql"
            @change="relayChange">
          </el-input>
        </el-form-item>        
        <el-form-item label="是否可手工转发">
          <el-radio-group v-model="form.relay.isManual" @change="relayChange">
            <el-radio :label="1">是</el-radio>
            <el-radio :label="0">否</el-radio>
          </el-radio-group>
        </el-form-item>
      </template>
      <el-divider v-if="userTask" content-position="center">通知提醒</el-divider>
      
      <el-form-item v-if="userTask" label="是否短信通知">
        <el-radio-group v-model="form.notice.isSmsNotice" @change="noticeChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="是否到期提醒">
        <el-radio-group v-model="form.notice.isDueNotice" @change="noticeChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item label="到期时间" v-if="userTask && form.notice.isDueNotice === 1">
        <el-input-number v-model="form.notice.dueDays" :precision="0" :step="1" @change="noticeChange"></el-input-number>&nbsp;工作日
      </el-form-item>
      <el-divider v-if="userTask">催办设置</el-divider>
      <el-form-item v-if="userTask" label="是否催办">
        <el-radio-group v-model="form.hasten.isHasten" @change="hastenChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <template v-if="userTask && form.hasten.isHasten == 1">
        <el-form-item label="时间字段">
          <el-select
            v-model="form.hasten.timeField"
            placeholder="请选择字段"
            clearable
            :style="{width: '100%'}"
            @change="hastenChange">
              <el-option v-for="item in columns" :key="item.columnId" :label="item.columnName +'：' +item.columnComment" :value="item.columnName" />
          </el-select>
        </el-form-item>
        <el-form-item label="相对天数">
          <el-input-number 
            v-model="form.hasten.days" 
            :precision="0" 
            :step="1" 
            @change="hastenChange">
          </el-input-number>&nbsp;天
        </el-form-item>
        <el-form-item label="是否短信通知">
          <el-radio-group v-model="form.hasten.isSmsNotice" @change="hastenChange">
            <el-radio :label="1">是</el-radio>
            <el-radio :label="0">否</el-radio>
          </el-radio-group>
        </el-form-item>
      </template>
      <template v-if="form.loopCharacteristics">
      <el-divider content-position="center">会签设置</el-divider>
      <el-form-item label="通过比例(%)">
        <el-slider v-model="form.countersign.ratio" @change="countersignChange"></el-slider>
      </el-form-item>
      <el-form-item label="是否一票权">
        <el-radio-group v-model="form.countersign.isOneVote" @change="countersignChange">
          <el-radio :label="0">否</el-radio>
          <el-radio :label="1">是</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="form.countersign.isOneVote == 1" label="一票权对象">
        <DeptPositionUser :selectValue="form.countersign.voteUser ? [form.countersign.voteUser] : []" @valueChange="countersignUserValueChange" />
      </el-form-item>
      </template>
      <el-divider v-if="userTask" content-position="center">分支参数</el-divider>
      <el-form-item v-if="userTask" label="分支参数">
        <el-select
          v-model="form.variableNames"
          multiple
          collapse-tags
          placeholder="请选择分支参数"
          @change="variableNamesChange"
          style="width: 100%;">
          <el-option
            v-for="item in columns" 
            :key="item.columnId" 
            :label="item.columnName +'：' +item.columnComment" 
            :value="item.columnName">
          </el-option>
        </el-select>
      </el-form-item>
      <el-divider v-if="userTask" content-position="center">节点事件</el-divider>
      <el-form-item v-if="userTask" label="是否回写">
        <el-radio-group v-model="form.isWriteBack" @change="isWriteBackChange">
          <el-radio :label="1">是</el-radio>
          <el-radio :label="0">否</el-radio>
        </el-radio-group>
      </el-form-item>
      <el-form-item v-if="userTask" label="前置事件">
        <el-input
          type="textarea"
          :rows="2"
          placeholder="请输入SQL"
          v-model="form.beforeEvent"
          @change="beforeEventChange">
        </el-input>
      </el-form-item>
      <el-form-item v-if="userTask" label="后置事件">
        <el-input
          type="textarea"
          :rows="2"
          placeholder="请输入SQL"
          v-model="form.afterEvent"
          @change="afterEventChange">
        </el-input>
      </el-form-item>
      <template v-if="sequenceFlow">
        <!-- 分支允许添加条件 -->
        <el-form-item label="分支条件">
          <el-input
            type="textarea"
            :rows="2"
            placeholder="请输入条件表达式"
            v-model="form.conditionExpression.body"
            @change="conditionExpressionChange">
          </el-input>
        </el-form-item>
      </template>
      <template v-if="callActivity">
        <!-- 选择外部子流程 -->
        <el-form-item label="选择子流程">
          <el-select v-model="form.calledElement" clearable placeholder="请选择子流程" @change="calledElementChange">
            <el-option v-for="item in processList" :key="item.key" :label="item.name" :value="item.key" />
          </el-select>
        </el-form-item>
        <el-form-item label="前置事件">
          <el-input
            type="textarea"
            :rows="2"
            placeholder="请输入SQL"
            v-model="form.startCallSql"
            @change="callSqlChange">
          </el-input>
        </el-form-item>
        <el-form-item label="后置事件">
          <el-input
            type="textarea"
            :rows="2"
            placeholder="请输入SQL"
            v-model="form.endCallSql"
            @change="callSqlChange">
          </el-input>
        </el-form-item>
      </template>
        
    </el-form>
    <el-dialog :visible.sync="layoutDialogVisible" title="选择表单布局">
      <FromLayout ref="FormLayout" :tableId="formTable.tableId" @callbackFormLayout="callbackFormLayout"/>
    </el-dialog>
    <el-dialog :visible.sync="printLayoutDialogVisible" title="选择打印布局">
      <PrintLayout ref="PrintLayout" @callbackPrintLayout="callbackPrintLayout"/>
    </el-dialog>
  </div>
</template>

<script>
// import FormTable from '@/views/form/components/FormTable'
import FromLayout from '@/views/workflow/form/components/FormLayout'
import PrintLayout from '@/views/workflow/components/PrintLayout'
import DeptPositionUser from '@/components/DeptPositionUser'
import DeptSelect from '@/components/DeptSelect'
import RoleSelect from '@/components/RoleSelect'

import enums from '@/views/workflow/utils/enum'
import { getListByTableId as getColumnsByTableId } from '@/api/workflow/form/columns'
import { getProcessList } from '@/api/workflow/bpmn/deploy'
export default {
  name: 'PropertyPanel',
  props: {
    modeler: {
      type: Object,
      required: true
    },
    formTable: {
      type: Object,
      default: function() {
        return {}
      }
    }
  },
  components: {
    FromLayout,
    PrintLayout,
    DeptPositionUser, // 部门岗位人员选择
    DeptSelect, // 部门树下拉框
    RoleSelect // 角色下拉框
  },
  data() {
    return {
      form: {
        id: '',
        name: '',
        userType: '',
        // color: null,
        formLayoutId: '', // 表单布局Id
        formLayoutName: '', // 表单布局名称
        operator: { // 操作人JSON
          optType: '',
          data: ''
        },
        countersign: { //会签设置
          ratio: 100, // 通过比例的比例值 0-100
          isOneVote: 0, // 是否一票权
          voteUser: null // 一票权用户
        },
        isAssignee: 0, // 是否指派
        isBack: 1, // 是否回退
        isClose: 0, // 是否终止
        isSignature: 1, // 是否显示签名
        isAutoComplete: 0, // 是否自动流转（仅限相邻节点为同一审核人时，前一节点审核后，后一节点自动审核）
        publicity: { // 转发设置
          isPublicity: 0, // 是否公示
          layoutId: '',
          layoutName: '', // 公示的表单布局名称
        },
        relay: { // 转发设置
          isRelay: 0,
          isManual: 0, // 是否手工转发，0否，1是
          layoutId: '',
          layoutName: '', // 转发的表单布局名称
          userSql: '', // 自动转发人员SQL
          userList: [] // 自动转发人员
        },
        notice: {
          isSmsNotice: 0, // 是否短信通知
          isDueNotice: 1, // 是否到期提醒
          dueDays: 0, // 节点处理的到期时间（工作日）
        },
        hasten: {
          isHasten: 0, // 是否催办
          timeField: '', // 对应（表单主表）的时间字段，如果不填，则取节点的创建时间
          days: 0, // 相对（时间字段的）天数
          isSmsNotice: 0, // 是否短信通知
        },
        variableNames: [], // 非分之流程的参数字段
        isWriteBack: 0, // 是否回写（用于明细表数据回写）
        beforeEvent: '', // 任务执行之前执行的SQL
        afterEvent: '', // 任务执行之后执行的SQL
        conditionExpression: {}, // 分支节点的条件
        calledElement: '', // 子流程id
        startCallSql: '', // 外部子流程前置事件（sql）
        endCallSql: '' // 外部子流程后置事件（sql）
      },
      columns: [], // 表单字段
      element: {}, // 当前操作节点
      processList: [], // 子流程列表
      // formTable: {}, // 对应的表单信息
      // formDialogVisible: false,
      layoutDialogVisible: false,
      isRelayLayoutDialog: false,
      isPublicityDialog: false,
      printLayoutDialogVisible: false
    }
  },
  watch: {
    'form.name': function(val, oldVal) {
      this.nameChange(val)
    },
    formTable: {
      handler(n, o) {
        this.getColumnsByTableId()
      },
      deep: true,
      immediate: true
    }
  },
  computed: {
    userTask() {
      if (!this.element) {
        return false
      }
      return this.element.type === 'bpmn:UserTask' // 用户任务
    },
    sequenceFlow() {
      if (!this.element) {
        return false
      }
      return this.element.type === 'bpmn:SequenceFlow' // 条件分支
    },
    callActivity() {
      if (!this.element) {
        return false
      }
      return this.element.type === 'bpmn:CallActivity' // 外部子流程
    },
    userTypeList() {  // 流程的节点操作人类型
      return enums.BPMN_USER_TYPE
    },
    relayList() { // 流程节点的转发类型
      return enums.BPMN_RELAY_TYPE
    },
    counterSignList() { // 流程节点的会签类型
      return enums.COUNTER_SIGN_TYPE
    }
  },
  created() {
    this.getColumnsByTableId()
    this.getProcessList()
  },
  methods: {
    async getColumnsByTableId() { // 获取表单字段列表
      if (!this.formTable.tableId) return
      const res = await getColumnsByTableId(this.formTable.tableId)
      this.columns = res && res.data ? res.data : []
    },
    handleFormLayout(type) { // 点击选择表单布局
      this.layoutDialogVisible = true
      this.isRelayLayoutDialog = false
      this.isPublicityDialog = false
      if (type === 'isRelay') { // 转发时选择表单布局
        this.isRelayLayoutDialog = true
      }
      if (type === 'isPublicity') { // 公示时选择表单布局
        this.isPublicityDialog = true
      }
    },
    callbackFormLayout(data) { // 选择表单布局回调
      if (this.isRelayLayoutDialog) { // 转发时选择表单布局的回调
        this.form.relay.layoutId = data.layoutId
        this.form.relay.layoutName = data.layoutName
        this.relayChange()
      } else if (this.isPublicityDialog) { // 公示时选择表单布局的回调
        this.form.publicity.layoutId = data.layoutId
        this.form.publicity.layoutName = data.layoutName
        this.publicityChange()
      } else {
        this.form.formLayoutId = data.layoutId
        this.form.formLayoutName = data.layoutName
        this.formLayoutChange()
      }
      this.layoutDialogVisible = false
    },
    handlePrintLayout() { // 点击选择打印布局
      this.printLayoutDialogVisible = true
    },
    callbackPrintLayout(data) { // 选择打印布局回调
      this.form.printLayout = data.name
      this.printLayoutDialogVisible = false
      this.updateProperties({ printLayout: data.name })
    },
    async getProcessList() { // 获取子流程列表
      const res = await getProcessList()
      this.processList = res && res.data ? res.data : []
    },
    operatorUserValueChange(selection) { // 选择节点操作人的指定人员
      this.form.operator.data = selection
      this.operatorDeptPosUserChange()
    },
    relayUserValueChange(selection) { // 选择部门岗位人员回调
      this.form.relay.userList =selection
      this.relayChange()
    },
    handleDeptPosUserRemove(index) { // 移除已选择的节点操作人
      this.form.operator.data.splice(index, 1)
      this.operatorDeptPosUserChange()
    },
    handleRelayUserListRemove(index) { // 移除已选择的转发人员
      this.form.relay.userList.splice(index, 1)
      this.relayChange()
    },
    handleModeler() {
      // 监听节点选择变化
      this.modeler.on('selection.changed', e => {
        const element = e.newSelection[0]
        this.element = element
        if (!element) return
        if (this.userTask) {
          this.handleUserTaskEle()
        } else if (this.sequenceFlow) {
          this.handleSequenceFlowEle()
        } else if (this.callActivity) {
          this.handleCallActivityEle()
        } else {
          this.form = {
            ...this.element.businessObject,
            ...this.element.businessObject.$attrs
          }
        }
      })

      //  监听节点属性变化
      this.modeler.on('element.changed', e => {
        const { element } = e
        if (!element) return
        this.element = element
        //  新增节点需要更新回属性面板
        if (element.id === this.form.id) {
          this.form.name = element.businessObject.name
          this.form = { ...this.form }
        }
        this.handleElement()
      })

      //  监听节点新增
      this.modeler.on('shape.added', e => { // 监听节点
        // if (!e.element) return
        // this.element = e.element
        // console.log('shape.added', this.element)
        // if (this.element.type === 'bpmn:Task' && !this.element.outgoing.length) { // 新增任务节点时，默认设置为用户节点
        //   this.element.type = 'bpmn:UserTask'
        //   this.form.name = '节点名称'
        //   this.form = { ...this.form }
        // }
      })
    },
    handleElement() {
      var moddle = this.modeler.get('moddle')
      if (this.element && this.element.businessObject) {
        if (this.element.type === 'bpmn:UserTask') {
          if (!this.element.businessObject.extensionElements 
          || (!this.element.businessObject.loopCharacteristics 
            && this.element.businessObject.extensionElements.values.
            filter(item => '${userTaskCreateListener}' === item.delegateExpression) <= 0
          )
          ) {  // 设置用户任务节点的属性和监听事件
            var extensionElements = moddle.create('bpmn:ExtensionElements')
            var taskListener = moddle.create('flowable:TaskListener', {
              event: 'create',
              delegateExpression: '${userTaskCreateListener}'
            })
            extensionElements.values = [ taskListener ]
            this.updateProperties({
              assignee: undefined,
              countersign: undefined,
              extensionElements: extensionElements
            })
          }
          // 设置会签属性，如果没有collection属性，说明是第一次设置
          else if (this.element.businessObject.loopCharacteristics 
          && !this.element.businessObject.loopCharacteristics['collection']) {
            /* // begin 这些内容是固定的 */
            this.element.businessObject.loopCharacteristics['collection'] = 'partyUserIdList'
            this.element.businessObject.loopCharacteristics['elementVariable'] = 'partyUserId'
            var newCondition = moddle.create('bpmn:Expression', {
              body: '${multiInstanceCompleteTask.condition(execution)}'
            })
            this.element.businessObject.loopCharacteristics['completionCondition'] = newCondition

            var extensionElements = moddle.create('bpmn:ExtensionElements')
            var taskListener = moddle.create('flowable:TaskListener', {
              event: 'create',
              delegateExpression: '${setMultiGroupsListener}'
            })
            extensionElements.values = [ taskListener ]
            this.updateProperties({ 
              assignee: '${partyUserId}',
              countersign: JSON.stringify(this.form.countersign),
              extensionElements: extensionElements
            })
            /* // end 这些内容是固定的 */
            // this.countersignChange() // 会签百分比、一票权设置初始化
            // this.updateProperties({ countersign: JSON.stringify(this.form.countersign) })
          }
        }
        else if (this.element.type === 'bpmn:CallActivity' 
        && !this.element.businessObject.extensionElements) { // 设置用户任务节点的属性和监听事件
          var extensionElements = moddle.create('bpmn:ExtensionElements')
          var taskListener = moddle.create('flowable:ExecutionListener', {
            event: 'start',
            delegateExpression: '${callActivityStartListener}'
          })
          extensionElements.values = [ taskListener ]
          this.updateProperties({ 
            extensionElements: extensionElements
          })
        }
      }
    },
    handleUserTaskEle() { // 操作用户任务节点
      if (!this.element.businessObject) return
      let operator = {
        optType: '',
        data: ''
      }
      if (this.element.businessObject.$attrs.operator) { // 解析节点操作人的格式，用以回显
        operator = JSON.parse(this.element.businessObject.$attrs.operator)
        if (operator && operator.data) { // 解析为页面组件可以绑定的值，用以回显
          if (operator.optType === Object.keys(enums.BPMN_USER_TYPE)[0]) { // 选择指定人员
            operator.data = operator.data ? operator.data : []
          } else if ([Object.keys(enums.BPMN_USER_TYPE)[2], Object.keys(enums.BPMN_USER_TYPE)[3]].indexOf(operator.optType) >= 0 ) { // 部门管理岗/部门管理人员
            const depts = []
            operator.data.forEach(item => {
              depts.push(item['deptId'])
            })
            operator.data = depts
          }else if (operator.optType === Object.keys(enums.BPMN_USER_TYPE)[4] ) { // 选择SQL语句
            operator.data = operator.data || ''
          }else if (operator.optType === Object.keys(enums.BPMN_USER_TYPE)[5] ) { // 指定角色
            operator.data = operator.data || ''
          }
        }
      }
      
      // 解析节点的转发设置，用以回显
      const relay = this.element.businessObject.$attrs.relay ? 
      JSON.parse(this.element.businessObject.$attrs.relay) : {
        isRelay: 0,
        isManual: 0,
        LayoutId: '',
        layoutName: '',
        userSql: '',
        userList: []
      }

      // 解析节点的通知设置，用以回显
      const notice = this.element.businessObject.$attrs.notice ? 
      JSON.parse(this.element.businessObject.$attrs.notice) : {
        isSmsNotice: 0, // 是否短信通知
        isDueNotice: 0, // 是否到期提醒
        dueDays: 0, // 节点处理的到期时间（工作日）
      }

      // 解析节点的催办设置，用以回显
      const hasten = this.element.businessObject.$attrs.hasten ? 
      JSON.parse(this.element.businessObject.$attrs.hasten) : {
        isHasten: 0, // 是否催办
        timeField: '', // 对应（表单主表）的时间字段，如果不填，则取节点的创建时间
        days: 0, // 相对（时间字段的）天数
        isSmsNotice: 0, // 是否短信通知
      }

      // 解析节点的公示设置，用以回显
      const publicity = this.element.businessObject.$attrs.publicity ? 
      JSON.parse(this.element.businessObject.$attrs.publicity) : {
        isPublicity: 0, // 是否公示
        layoutId: '',
        layoutName: '', // 公示的表单布局名称
      }
      const countersign = this.element.businessObject.$attrs.countersign ? 
        JSON.parse(this.element.businessObject.$attrs.countersign) : { //会签设置
          ratio: 100, // 通过比例的比例值 0-100
          isOneVote: 0, // 是否一票权
          voteUser: {} // 一票权用户
        }

      // 解析节点的分支参数设置，用以回显
      const variableNames = this.element.businessObject.$attrs.variableNames ? 
      this.element.businessObject.$attrs.variableNames.split(',') : []

      this.form = {
        ...this.element.businessObject,
        ...this.element.businessObject.$attrs,
        operator: operator,
        relay: relay,
        notice: notice,
        hasten: hasten,
        publicity: publicity,
        countersign: countersign,
        variableNames: variableNames
      }
      // 字符串或undefined转换为数字
      this.form.isAssignee = +this.form.isAssignee || 0
      this.form.isBack = +this.form.isBack || 0
      this.form.isClose = +this.form.isClose || 0
      this.form.isSignature = +this.form.isSignature || 0
      this.form.isAutoComplete = +this.form.isAutoComplete || 0
      this.form.isWriteBack = +this.form.isWriteBack || 0
    },
    handleSequenceFlowEle() { // 操作分支节点
      if (!this.element.businessObject) return
      const conditionExpression = this.element.businessObject.conditionExpression ? 
      JSON.parse(JSON.stringify(this.element.businessObject.conditionExpression)) : {
        body: ''
      }
      this.form = {
        ...this.element.businessObject,
        ...this.element.businessObject.$attrs,
        conditionExpression: conditionExpression
      }
    },
    handleCallActivityEle() { // 操作外部子流程节点
      if (!this.element.businessObject) return
      const obj = this.element.businessObject
      this.form = {
        ...obj,
        ...obj.$attrs,
        startCallSql: '',
        endCallSql: ''
      }
      if (obj.extensionElements && obj.extensionElements.values && obj.extensionElements.values.length) {
        const startListener = obj.extensionElements.values.find(item => item.$type === 'flowable:ExecutionListener' && item.event === 'start')
        if (startListener && startListener.fields && startListener.fields.length) {
          const field = startListener.fields.find(item => item.$type === 'flowable:Field' && item.name === 'callActivitySql')
          if (field) {
            this.form.startCallSql = field.stringValue
          }
        }
        const endListener = obj.extensionElements.values.find(item => item.$type === 'flowable:ExecutionListener' && item.event === 'end')
        if (endListener && endListener.fields && endListener.fields.length) {
          const field = endListener.fields.find(item => item.$type === 'flowable:Field' && item.name === 'callActivitySql')
          if (field) {
            this.form.endCallSql = field.stringValue
          }
        }
      }
    },
    // 属性面板名称，更新回流程节点
    nameChange(name) {
      const modeling = this.modeler.get('modeling')
      modeling.updateLabel(this.element, name)
    },
    // 属性面板表单布局，更新回流程节点
    formLayoutChange() {
      this.updateProperties({ formLayoutId: this.form.formLayoutId, formLayoutName: this.form.formLayoutName })
    },
    // 属性面板颜色，更新回流程节点
    colorChange(color) {
      const modeling = this.modeler.get('modeling')
      modeling.setColor(this.element, {
        fill: null,
        stroke: color
      })
      this.updateProperties({ color: color })
    },
    // 切换操作人类型，更新回流程节点
    userTypeChange(value) {
      if (value === Object.keys(enums.BPMN_USER_TYPE)[0]) { // 选择指定人员
        this.form.operator.data = []
      } else {
        this.form.operator.data = ''
      }
      const json = { optType: value, data: this.form.operator.data } // 每次改变userType时，清空data 
      this.updateProperties({ operator: JSON.stringify(json) })
    },
    operatorDeptPosUserChange() { // 属性面板操作人为指定人员时，更新回流程节点
      // 格式为接口识别的格式，用以提交保存数据
      const json = { optType: this.form.operator.optType, data: this.form.operator.data }
      this.updateProperties({ operator: JSON.stringify(json) })
    },
    operatorDeptChange(value) { // 属性面板操作人为部门管理岗/部门管理人时，更新回流程节点
      let data= []
      // 格式为接口识别的格式，用以提交保存数据
      if (value && value.length) {
        value.forEach(item => {
          data.push({ deptId: item })
        })
      }
      const json = { optType: this.form.operator.optType, data: [...data] }
      this.updateProperties({ operator: JSON.stringify(json) })
    },
    operatorSQLChange(value) { // 属性面板操作人为SQL语句时，更新回流程节点
      const json = { optType: this.form.operator.optType, data: value }
      this.updateProperties({ operator: JSON.stringify(json) })
    },
    roleChange(value) { // 选择角色人员回调
      const json = { optType: this.form.operator.optType, data: value  }
      this.updateProperties({ operator: JSON.stringify(json) })
    },
    isAssigneeChange(value) { // 是否指派
      this.updateProperties({ isAssignee: value })
    },
    isBackChange(value) { // 是否回退
      this.updateProperties({ isBack: value })
    },
    isCloseChange(value) { // 是否终止
      this.updateProperties({ isClose: value })
    },
    isSignatureChange(value) { // 是否显示签名
      this.updateProperties({ isSignature: value })
    },
    isAutoCompleteChange(value) { // 是否自动流转
      this.updateProperties({ isAutoComplete: value })
    },
    publicityChange(value) { // 是否公示
      const jsonStr = JSON.stringify(this.form.publicity)
      this.updateProperties({ publicity: jsonStr })
    },
    noticeChange() { // 提醒设置
      const jsonStr = JSON.stringify(this.form.notice)
      this.updateProperties({ notice: jsonStr })
    },
    hastenChange() { // 催办设置
      const jsonStr = JSON.stringify(this.form.hasten)
      this.updateProperties({ hasten: jsonStr })
    },
    relayChange() { // 转发设置
      const jsonStr = JSON.stringify(this.form.relay)
      this.updateProperties({ relay: jsonStr })
    },
    countersignUserValueChange(selection) {
      this.form.countersign.voteUser = selection && selection.length ? selection[0] : null
      this.countersignChange()
    },
    countersignChange() { // 会签设置
      this.updateProperties({ countersign: JSON.stringify(this.form.countersign) })
      this.handleElement()
    },
    variableNamesChange(value) { // 分支流程的参数字段
      this.updateProperties({ variableNames: value.toString() })
    },
    isWriteBackChange(value){ // 是否回写（明细表数据）
      this.updateProperties({ isWriteBack: value })
    },
    beforeEventChange(value){ // 前置事件
      this.updateProperties({ beforeEvent: value })
    },
    afterEventChange(value){ // 后置事件
      this.updateProperties({ afterEvent: value })
    },
    conditionExpressionChange(value) { // 分支节点的条件表达式修改事件

      var moddle = this.modeler.get('moddle')
      var newCondition = moddle.create('bpmn:Expression', {
        body: value
      })
      const json = { conditionExpression: newCondition }
      this.updateProperties(json)
    },
    calledElementChange(value){ // 选择子流程
      this.updateProperties({ calledElement: value, 'flowable:inheritVariables': true })
    },
    callSqlChange(){ // 输入子流程数据源（sql）
      var moddle = this.modeler.get('moddle')
      var extensionElements = moddle.create('bpmn:ExtensionElements')
      extensionElements.values = []
      // 前置事件
      if (this.form.startCallSql) {
        var startCallSql = moddle.create('flowable:Field', {
          name: 'callActivitySql',
          stringValue: this.form.startCallSql
        })
        var startTaskListener = moddle.create('flowable:ExecutionListener', {
          event: 'start',
          delegateExpression: '${callActivityStartListener}'
        })
        startTaskListener.fields = [ startCallSql ]
        extensionElements.values.push(startTaskListener)
      }

      // 后置事件
      if (this.form.endCallSql) {
        var endCallSql = moddle.create('flowable:Field', {
          name: 'callActivitySql',
          stringValue: this.form.endCallSql
        })
        var endTaskListener = moddle.create('flowable:ExecutionListener', {
          event: 'end',
          delegateExpression: '${callActivityEndListener}'
        })
        endTaskListener.fields = [ endCallSql ]
        extensionElements.values.push(endTaskListener)
      }
      this.updateProperties({ 
        extensionElements: extensionElements
      })
    },
    // 在这里我们封装一个通用的更新节点属性的方法
    updateProperties(properties) {
      const modeling = this.modeler.get('modeling')
      modeling.updateProperties(this.element, properties)
    },
    // 在这里我们封装一个通用的删除节点属性的方法
    removeProperty(property) {
      const modeling = this.modeler.get('modeling')
      delete this.element.businessObject[property]
    }
  },
  mounted() {
    this.handleModeler()
  }
}
</script>

<style lang="scss" scoped>
.property-panel {
  position: absolute;
  right: 0px;
  top: 0;
  background: #fff;
  border-left: 1px solid #f1e8e8;
  padding: 0 10px;
  width: 300px;
  height: 100%;
  overflow: auto;
}
</style>
